package com.inkkpot.prettyprint;

import org.htmlparser.*;
import org.htmlparser.lexer.Lexer;
import org.htmlparser.nodes.TagNode;
import org.htmlparser.tags.*;
import org.htmlparser.util.NodeList;
import org.htmlparser.util.ParserException;

public class PrettyPrintHelper {
	public static String coreUrl = "/print?url=";
	public static ScriptTag jqueryMinScript = new ScriptTag();
	public static Tag scriptEndTag = new TagNode();
	public static ScriptTag jqueryUiMinScript= new ScriptTag();
	public static ScriptTag jqueryPrintScript = new ScriptTag();
	public static ScriptTag jqueryEditScript = new ScriptTag();
	public static ScriptTag inkkpotPrintScript = new ScriptTag();
	public static StyleTag inkkpotPrintStyle = new StyleTag();
	public static Tag styleEndTag = new TagNode();

	static{
	jqueryMinScript.setAttribute("src", "/js/jquery-min.js");
	scriptEndTag.setTagName("/"+jqueryMinScript.getTagName());
  //end tag attribute needs to be set otherwise it doesn't let other script tags get loaded
	jqueryMinScript.setEndTag(scriptEndTag);
	
	jqueryUiMinScript.setAttribute("src", "/js/jquery-ui-min.js");
	jqueryUiMinScript.setEndTag(scriptEndTag);
	
	jqueryPrintScript.setAttribute("src","/js/jquery-printElement.js");
	jqueryPrintScript.setEndTag(scriptEndTag);
	
	inkkpotPrintScript.setAttribute("src", "/js/inkkpot-print.js");
	inkkpotPrintScript.setEndTag(scriptEndTag);
	
	jqueryEditScript.setAttribute("src","/js/jquery-jeditable.js");
	jqueryEditScript.setEndTag(scriptEndTag);
	
	inkkpotPrintStyle.setTagName("link");
	styleEndTag.setTagName("/"+inkkpotPrintStyle.getTagName());
	inkkpotPrintStyle.setAttribute("rel","stylesheet");
	inkkpotPrintStyle.setAttribute("href","/css/inkkpot-print.css");
	inkkpotPrintStyle.setAttribute("type","text/css");
	inkkpotPrintStyle.setEndTag(styleEndTag);
	}
	
	/**
	 * This method creates the html page from the html content passed to it.
	 * The htmlContent passed should be raw html as fetched from a url.
	 * The method would add modifications to the content to add pretty print functionality
	 * @return
	 */
	public static String getHTML(String htmlContent, String baseUrl){
		htmlContent = sanitzeLinks(htmlContent, baseUrl);
		return htmlContent;
	}
	
	private static String sanitzeLinks(String htmlContent, String baseUrl){
		StringBuilder pageContent = new StringBuilder();
		String customUrl = baseUrl;
		try{
			Parser parser = new Parser(htmlContent);
			Lexer lexer = parser.getLexer();
			Node node = lexer.nextNode();
			while(node != null){
				processNodes(node, customUrl);
				pageContent.append(node.toHtml());
				node = lexer.nextNode();
			}
		}catch(ParserException pe){
			return htmlContent;
		}
		return pageContent.toString();
	}
	
	private static void processNodes(Node node, String customUrl){
		if(node == null){
			return;
		}
		//processing head tag
		//adding custom scripts to head
		if(node instanceof HeadTag){
			HeadTag head = (HeadTag)node;
			NodeList list = head.getChildren();
			if(list == null){
				list = new NodeList();
			}
			list.add(jqueryMinScript);
			list.add(jqueryUiMinScript);
			list.add(inkkpotPrintScript);
			list.add(jqueryPrintScript);
			list.add(jqueryEditScript);
			list.add(inkkpotPrintStyle);
			head.setChildren(list);
		}
		//encrypting links so that on click of links on page it opens routed to our server
		//also relative path links sanitized to make full url links
		else if(node instanceof LinkTag){
			LinkTag link = (LinkTag)node;
			link.setLink(encryptLink(link.getLink(), customUrl));
		}
		//relative path image url resolving to full path
		else if(node instanceof ImageTag){
			ImageTag img = (ImageTag)node;
			img.setImageURL(sanitizeImageUrl(img.getImageURL(), customUrl));
		}
		//scripts on the page need to be removed
		//we would be adding our custom scripts so no need of these scripts
		else if(node instanceof ScriptTag){
			ScriptTag script = (ScriptTag)node;
			//TODO:
		}
		
		if(node.getChildren() != null)
		for(Node childNode:node.getChildren().toNodeArray()){
			processNodes(childNode, customUrl);
		}
	}
	
	private static String encryptLink(String link, String customUrl){
//		if(link.startsWith("http://")){
//			link = coreUrl + link;
//		}else if(link.startsWith("/")){
//			link = coreUrl + customUrl+link;
//		}
		return "";
	}
	
	private static String sanitizeImageUrl(String link, String customUrl){
		if(link.startsWith("/")){
			return customUrl+link;
		}
		return link;
	}
}
